package com.cuiweiyou.gimmick;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Point;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.WindowEvent;
import java.util.ArrayList;
import java.util.List;

import javax.swing.Box;
import javax.swing.DefaultListCellRenderer;
import javax.swing.DefaultListModel;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JPanel;
import javax.swing.JScrollBar;
import javax.swing.JScrollPane;
import javax.swing.JSeparator;
import javax.swing.JTextArea;
import javax.swing.SwingConstants;

public class ChattestUI extends JFrame {
    private JFrame parentWindow;

    private int frameWidth;
    private int frameHeight;

    private List<GimmickBean> gimmickList;
    private JButton sendButton;
    private JButton restartButton;
    private JTextArea messageTextArea;
    private JList messageListView;
    private JScrollPane messageScrollPanel;

    public ChattestUI(JFrame frame, List<GimmickBean> gimmicks) {
        super("模拟对话");
        System.out.println("模拟对话");

        this.gimmickList = gimmicks;
        this.parentWindow = frame;
        this.parentWindow.setEnabled(false);

        setDefaultLookAndFeelDecorated(true);
        setAlwaysOnTop(true);

        Dimension dimension = Toolkit.getDefaultToolkit()
                                     .getScreenSize();
        frameWidth = (int) (dimension.getWidth() / 2);
        frameHeight = (int) (dimension.getHeight() / 2);
        setSize(frameWidth, frameHeight);
        int x = (int) (dimension.getWidth() / 2 - frameWidth / 2);
        int y = (int) (dimension.getHeight() / 2 - frameHeight / 2);
        setDefaultCloseOperation(JFrame.DO_NOTHING_ON_CLOSE);
        setResizable(false);
        setLocation(x, y);
        setSize(frameWidth, frameHeight);

        initData();
        initView();
        initEvent();

        setVisible(true);
    }

    private void initEvent() {
        sendButton.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent actionEvent) {
                sendMessage();
            }
        });

        restartButton.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent actionEvent) {
                reStartChat();
            }
        });
    }

    private void initData() {
        TalkMaster.getInstance()
                  .setGimmickList(gimmickList);
    }

    @Override
    protected void processWindowEvent(WindowEvent windowEvent) {
        System.out.println("processWindowEvent");

        if (windowEvent.getID() == WindowEvent.WINDOW_CLOSING) {
            parentWindow.setEnabled(true);
            dispose();
        } else if (windowEvent.getID() == WindowEvent.WINDOW_OPENED) {
            if (null != messageTextArea) {
                messageTextArea.requestFocus();
            }
        }

        super.processWindowEvent(windowEvent);
    }

    private void initView() {
        int messagePanelWidth = frameWidth;
        int messagePanelHeight = frameHeight / 3 * 2;
        int separatorHeight = 5;
        int editPanelWidth = frameWidth;
        int editPanelHeight = frameHeight - messagePanelHeight - separatorHeight - 30;

        Box verticalBox = Box.createVerticalBox();
        verticalBox.add(getMessagePanel(messagePanelWidth, messagePanelHeight));
        verticalBox.add(getSeparator(frameWidth, separatorHeight, Color.LIGHT_GRAY));
        verticalBox.add(getEditPanel(editPanelWidth, editPanelHeight));

        setContentPane(verticalBox);
    }

    private Component getMessagePanel(int panelWidth, int panelHeight) {
        messageListView = new JList();
        messageListView.setCellRenderer(new DefaultListCellRenderer() {
            private Color ffffccColor = new Color(Integer.valueOf("#ffffcc".substring(1), 16));
            private Color ccffffColor = new Color(Integer.valueOf("#ccffff".substring(1), 16));

            @Override
            public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
                super.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
                if (index % 2 == 0) {
                    setBackground(ffffccColor);
                } else if (index % 2 == 1) {
                    setBackground(ccffffColor);
                }

                return this;
            }
        });
        messageListView.setModel(new DefaultListModel<String>());
        messageListView.setFixedCellHeight(30);

        messageScrollPanel = new JScrollPane(messageListView);
        messageScrollPanel.setPreferredSize(new Dimension(panelWidth, panelHeight));

        return messageScrollPanel;
    }

    private Component getEditPanel(int panelWidth, int panelHeight) {
        int textAreaPanelWidth = panelWidth / 4 * 3;
        int textAreaPanelHeight = panelHeight;
        int sendPanelWidth = panelWidth - textAreaPanelWidth;
        int sendPanelHeight = panelHeight;

        Component textAreaPanel = getTextAreaPanel(textAreaPanelWidth, textAreaPanelHeight);
        Component sendPanel = getSendPanel(sendPanelWidth, sendPanelHeight);

        JPanel editPanel = new JPanel();
        editPanel.setPreferredSize(new Dimension(panelWidth, panelHeight));
        editPanel.setLayout(new BorderLayout());
        editPanel.add(BorderLayout.WEST, textAreaPanel);
        editPanel.add(BorderLayout.EAST, sendPanel);

        return editPanel;
    }

    private Component getTextAreaPanel(int panelWidth, int panelHeight) {
        messageTextArea = new JTextArea();
        messageTextArea.setLineWrap(true);

        JScrollPane messageScrollPanel = new JScrollPane(messageTextArea);
        messageScrollPanel.setPreferredSize(new Dimension(panelWidth, panelHeight));

        return messageScrollPanel;
    }

    private Component getSendPanel(int panelWidth, int panelHeight) {
        int noteLabelWidth = panelWidth;
        int noteLabelHeight = 30;
        int sendButtonWidth = 90;
        int sendButtonHeight = 30;
        int restartButtonWidth = 90;
        int restartButtonHeight = 30;
        int emptyWidth = 90;
        int emptyHeight = panelHeight - noteLabelHeight - sendButtonHeight - restartButtonHeight - 20;

        JLabel noteLabel = new JLabel("模拟客户进行聊天");
        noteLabel.setPreferredSize(new Dimension(noteLabelWidth, noteLabelHeight));
        noteLabel.setHorizontalAlignment(SwingConstants.CENTER);
        sendButton = new JButton("发送");
        sendButton.setPreferredSize(new Dimension(sendButtonWidth, sendButtonHeight));
        restartButton = new JButton("重新开始");
        restartButton.setPreferredSize(new Dimension(restartButtonWidth, restartButtonHeight));

        JPanel sendPanel = new JPanel();
        sendPanel.setPreferredSize(new Dimension(panelWidth, panelHeight));
        sendPanel.setBackground(Color.WHITE);
        sendPanel.add(noteLabel);
        sendPanel.add(sendButton);
        sendPanel.add(getSeparator(emptyWidth, emptyHeight, Color.WHITE));
        sendPanel.add(restartButton);

        return sendPanel;
    }

    private Component getSeparator(int separatorWidth, int separatorHeight, Color color) {
        JSeparator separator = new JSeparator(SwingConstants.CENTER);
        separator.setPreferredSize(new Dimension(separatorWidth, separatorHeight));
        separator.setBackground(Color.WHITE);
        separator.setForeground(color);

        return separator;
    }

    private void sendMessage() {
        String text = messageTextArea.getText();
        if (null == text || text.length() < 1) {
            return;
        }

        messageTextArea.setText("");
        messageTextArea.requestFocus();

        text = text.trim();

        String spliteFlag = "<<>>";
        if (text.contains("\r\n") || text.contains("\n")) {
            text = text.replace("\r\n", spliteFlag)
                       .replace("\n", spliteFlag);
        }
        String[] questions = text.split(spliteFlag);
        List<String> questionList = new ArrayList<>();
        if (questions.length > 0) {
            for (int i = 0; i < questions.length; i++) {
                questionList.add(questions[i]);
            }
        }

        addMessageToListView(questionList);

        List<String> ansers = TalkMaster.getInstance()
                                        .getAnswer(questionList);

        addMessageToListView(ansers);
    }

    private void reStartChat() {
        ((DefaultListModel) messageListView.getModel()).removeAllElements();
    }

    private void addMessageToListView(List<String> msgs) {
        for (int i = 0; i < msgs.size(); i++) {
            String msg = msgs.get(i);
            addMessageToListView(msg);
        }
    }

    private void addMessageToListView(String msg) {
        DefaultListModel<String> listModel = (DefaultListModel<String>) messageListView.getModel();
        listModel.addElement(msg);

        JScrollBar scrollBar = messageScrollPanel.getVerticalScrollBar();
        messageScrollPanel.getViewport()
                          .setViewPosition(new Point(0, scrollBar.getMaximum()));
    }
}
